﻿using System;
using System.Collections.Generic;

using MBT.Modeling;
using SMLib.Base;

namespace MBT.TestStateLevel
{
    public class TA_State :
        IState<TA_State.TA_Transition>,
        IContainedObject
    {
        /// <summary>
        /// State identifier (an increasing integer number, starting from 0
        /// </summary>
        public int id;

        /// <summary>
        /// Is this a final state? (isFinal is evaluated as "true" in this state)
        /// </summary>
        public bool finalState = false;

        /// <summary>
        /// List of outgonig transitions from this state
        /// </summary>
        public List<TA_Transition> transitions = new List<TA_Transition>();

        /// <summary>
        /// The object containing state variables
        /// </summary>
        public object state;

        public override string ToString()
        {
            return id.ToString();
        }
		
        /// <summary>
        /// Check that is there any transition with a special label
        /// Check that is any variant of an action is enabled or not
        /// Used in state space generation using a mask state space (composition)
        /// </summary>
        /// <param name="label"></param>
        /// <returns></returns>
        public bool HasTransition(string label)
        {
            for (int i = 0; i < transitions.Count; i++)
            {
                if ((transitions[i]).actionName.Equals(label))
                    return true;
            }
            return false;
        }

        public TA_State next(string label)
        {
            for (int i = 0; i < transitions.Count; i++)
            {
                if ((transitions[i]).actionName.Equals(label))
                    return (transitions[i]).DestinationState;
            }
            return null;
        }


        public class TA_Transition //: SMLib.Base.ITransition<TestState> //: ITransition
        {
            //* everything can goes into ActionParameter->Then we can use DIGRAPH directly!!!
            public TA_Transition(TA_State to, string actionName, bool controllable, ActionInfo parameters)
            {
                this.DestinationState = to;
                this.actionName = actionName;
                //this.rate = 0;
                isControllable = controllable;
                this.parameters = parameters;
            }
            public override string ToString()
            {
                return actionName + parameters.ToString();
            }
            /// <summary>
            /// Destination of transition
            /// </summary>
            public TA_State DestinationState;

            /// <summary>
            /// Name of action [To Do:also exists in parameters, remove this variable]
            /// </summary>
            public string actionName;

            /// <summary>
            /// Transition is controllable or observable [To Do:also exists in parameters, remove this variable]
            /// </summary>
            public bool isControllable;

            /// <summary>
            /// What event or action is this? with which parameters?
            /// </summary>
            public ActionInfo parameters;//=new ActionInfo("");


            #region Itransition Members

            public TA_State Destination
            {
                get { return DestinationState; }
                set { DestinationState = value; }
            }

            #endregion


        }

        #region IStateContainer Members

        public object Identifier
        {
            get { return id; }
        }

        public string ModelName
        {
            get { return ""; }
        }

        public List<TA_Transition> Transitions
        {
            get { return transitions; }
        }

        public object content
        {
            get { return state; }
        }

        #endregion

        #region IContainedObject Members

        public object Content
        {
            get { return state; }
        }

        #endregion
    }
}
